package cqu.ioc.BeanUtil;


import cqu.ioc.Register;
import cqu.ioc.annotation.Component;
import cqu.mvc.annotation.Controller;

import java.io.File;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.Properties;

/**
 * 读取需要扫描的包并注册bean
 */
public class Parser {

    public static final String SCAN_PACKAGE = "scanPackage";


    private Register register;

    public Parser(Register register){
        this.register = register;
    }

    public void parse(Properties properties){
        String packageName = properties.getProperty(SCAN_PACKAGE);
        doRegister(packageName);
    }


    private void doRegister(String packageName) {
        URL url = getClass().getClassLoader().getResource("./"+packageName.replaceAll("\\.","/"));
        File dir = new File(url.getFile());
        for (File file:dir.listFiles()){
            if(file.isDirectory()){
                doRegister(packageName+"."+file.getName());
            }else {
                String className = packageName+"."+file.getName().replaceAll(".class","").trim();
                List<Bean> definitions = generate(className);
                if(definitions == null)continue;
                this.register.registerBeanDefinition(definitions);
            }
        }

    }

    public static List<Bean> generate(String className) {
        try {
            Class clazz = Class.forName(className);
            String[] ids = generateIds(clazz);
            if (ids == null) return null;
            List<Bean> list = new ArrayList<Bean>();
            for (String id : ids) {
                list.add(new Bean(id, clazz));
            }
            return list;
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
        return null;
    }



    private static String[] generateIds(Class clazz) {
        String[] ids = null;
        if (clazz.isAnnotationPresent(Controller.class)) {
            ids = new String[]{clazz.getName()};
        } else if (clazz.isAnnotationPresent(Component.class)) {
            Component component = (Component) clazz.getAnnotation(Component.class);
            String value = component.value();
            if (!"".equals(value)) {
                ids = new String[]{value};
            } else {
                Class<?>[] interfaces = clazz.getInterfaces();
                ids = new String[interfaces.length];
                for (int i = 0; i < interfaces.length; i++) {
                    ids[i] = interfaces[i].getName();
                }
                return ids;
            }
        }
        return ids;
    }
}